package org.wu.framework.lazy.orm.core.persistence.format;

import org.wu.framework.core.NormalUsedString;
import org.wu.framework.core.ReflexUtils;
import org.wu.framework.core.utils.BeanTypeUtil;
import org.wu.framework.core.utils.DataTransformUntil;

import java.util.*;
import java.util.stream.Collectors;

/**
 * foreach标签格式化
 * <span>
 *      <foreach collection="list" index="index" item="item" open="" close="" separator="">
 *               <el-form-item label="#{item.label}" prop="#{item.prop}">
 *                   <el-input v-model="#{item.prop}" placeholder="" clearable></el-input>
 *               </el-form-item>
 *           </foreach>
 * </span>
 */
public class ForEachFormatMapper extends AbstractFormatMapper implements FormatMapper {

    String first_split = "<foreach";
    String latest_split = "</foreach>";

    /**
     * 格式化
     *
     * @param pattern 文件数据
     * @param param   参数
     */
    @Override
    public String format(String pattern, Object param) {
        StringBuilder stringBuilder = new StringBuilder();
        String[] splitList = pattern.split(latest_split);
        for (String itemSplit : splitList) {
            if (itemSplit.contains(first_split)) {
                int first_first = itemSplit.lastIndexOf(first_split);
                String foreach_before = itemSplit.substring(0, first_first);
                stringBuilder.append(foreach_before);
                String foreach_item = itemSplit.substring(first_first);
                int foreach_start_end_index = foreach_item.indexOf(NormalUsedString.RIGHT_CHEV);
                int first_end = first_first + foreach_start_end_index;
                // 获取 collection、index、item、open、close、separator
                String foreach_prop = itemSplit.substring(first_first + first_split.length(), first_end);

                String collectionName = "";
                String indexName = "";
                String itemName = "";
                String open = "";
                String close = "";
                String separator = "";
                for (String prop_k_v : foreach_prop.split(NormalUsedString.SPACE)) {

                    String[] split = prop_k_v.split(NormalUsedString.EQUALS);
                    if (split.length == 2) {
                        String k = split[0];
                        String v = split[1].replaceAll(NormalUsedString.DOUBLE_QUOTE, "");
                        // collection、index、item、open、close、separator
                        switch (k) {
                            case "collection":
                                collectionName = v;
                                break;
                            case "index":
                                indexName = v;
                                break;
                            case "item":
                                itemName = v;
                                break;
                            case "open":
                                open = v;
                                break;
                            case "close":
                                close = v;
                                break;
                            case "separator":
                                separator = v;
                                break;
                        }
                    }
                }

                String itemPattern = itemSplit.substring(first_end + 1).replaceAll(latest_split, "");


                Object collection = ReflexUtils.invokeDeclaredFieldWithDeep(param, collectionName);
                if (collection instanceof Collection) {
                    List<?> collectionList = (List<?>) collection;

                    stringBuilder.append(open);

                    // item 属性替换
                    List<String> itemFormatList = new ArrayList<>();
                    for (int i = 0; i < collectionList.size(); i++) {
                        Object item = collectionList.get(i);
                        Map<String, Object> itemMap = new HashMap<>();
                        itemMap.put(itemName, item);
                        itemMap.put(indexName, i);
                        // item Map支持二级属性
                        if (item instanceof Map) {
                            for (Map.Entry<?, ?> entry : ((Map<?, ?>) item).entrySet()) {
                                Object k = entry.getKey();
                                Object v = entry.getValue();
                                itemMap.put(itemName + NormalUsedString.DOT + k, v);
                            }
                        }
                        // item 对象支持二级属性
                        if (BeanTypeUtil.isNotJavaBean(item.getClass())) {
                            HashMap<String, Object> hashMap = DataTransformUntil.transformBean(item, HashMap.class);
                            for (Map.Entry<String, Object> stringObjectEntry : hashMap.entrySet()) {
                                String k = stringObjectEntry.getKey();
                                Object v = stringObjectEntry.getValue();
                                itemMap.put(itemName + NormalUsedString.DOT + k, v);
                            }
                        }

                        String format = super.format(itemPattern, itemMap);
                        itemFormatList.add(format);

                    }
                    stringBuilder.append(String.join(separator, itemFormatList));
                    stringBuilder.append(close);

                } else {
                    // 数据不是数组
                    stringBuilder.append(itemSplit);
                }
            } else {
                // 直接拼接
                stringBuilder.append(itemSplit);
            }

        }
        // 截取</foreach>
        // 获取item内容、collection、index、item、open、close、separator
        // 替换中间行数据为新的数据
        return stringBuilder.toString();
    }
}